﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Simple.Common.Authentication;
using Simple.Services.System.FileInfo;

namespace Simple.Services.System
{
    /// <summary>
    /// 园长热线
    /// </summary>
    public class PrincipalHotlineService : BusinessBaseService
    {
        private readonly SimpleDbContext _context;
        private readonly FileInfoService _fileInfoService;


        public PrincipalHotlineService(SimpleDbContext context,
            ISimpleService services,
            FileInfoService fileInfoService) : base(services)
        {
            _context = context;
            _fileInfoService = fileInfoService;
        }

        /// <summary>
        /// 分页查询
        /// </summary>
        /// <param name="input"></param>
        /// <param name="IsParent"></param>
        /// <returns></returns>
        public async Task<PageResultModel<PrincipalHotlineDto>> GetPage(PrincipalHotlinePageInput input, bool IsParent = false)
        {
            var result = new PageResultModel<PrincipalHotlineDto>();
            var query = (await OrganizationFilter(_context.Set<PrincipalHotline>())).Include(p => p.Images).Include(p => p.ReplyList).AsQueryable();
            if (IsParent)
            {
                var childId = _currentUser?.FindClaimValue(SimpleClaimTypes.ChildId);
                if (!string.IsNullOrWhiteSpace(childId))
                {
                    query = query.Where(p => p.ChildId.ToString() == childId);
                }
                else
                {
                    return result;
                }
            }
            else
            {
                if (input.ClassIdList != null && input.ClassIdList.Any())
                {
                    query = query.Where(p => input.ClassIdList.Contains(p.ClassId));
                }
                if (input.StartTime.HasValue)
                {
                    query = query.Where(p => p.CreatedTime.Value.Date >= input.StartTime.Value.Date);
                }
                if (input.EndTime.HasValue)
                {
                    query = query.Where(p => p.CreatedTime.Value.Date <= input.EndTime.Value.Date);
                }
                if (input.IsReply.HasValue)
                {
                    query = query.Where(p => p.IsReply == input.IsReply);
                }
            }
            // 获取总数量
            result.TotalRows = await query.CountAsync();

            // 分页查询
            query = query.OrderByDescending(u => u.CreatedTime).Page(input.PageNo, input.PageSize);
            var lstEntity = await query.ToListAsync();
            var lstDto = MapperHelper.Map<List<PrincipalHotlineDto>>(lstEntity);
            lstDto = Completion(lstDto);
            result.Rows = lstDto;

            result.SetPage(input);
            result.CountTotalPage();

            return result;
        }

        /// <summary>
        /// 详情
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<PrincipalHotlineDto> GetAsync(Guid id)
        {
            var entity = await _context.Set<PrincipalHotline>().Include(p => p.Images).Include(p => p.ReplyList).FirstOrDefaultAsync(p => p.Id == id);
            if (entity == null)
            {
                throw AppResultException.Status500InternalServerError("没有找到该热线记录");
            }
            var dto = MapperHelper.Map<PrincipalHotlineDto>(entity);
            dto = Completion(new List<PrincipalHotlineDto>() { dto }).FirstOrDefault();
            return dto;
        }

        /// <summary>
        /// 完善
        /// </summary>
        /// <param name="lstDto"></param>
        /// <returns></returns>
        public List<PrincipalHotlineDto> Completion(List<PrincipalHotlineDto> lstDto)
        {
            return (from m in lstDto
                    join c in _context.Set<Childrens>().AsQueryable() on m.ChildId equals c.Id into mc
                    join cl in _context.Set<SysClasses>().AsQueryable() on m.ClassId equals cl.Id into mcl
                    join p in _context.Set<Parent>().AsQueryable() on m.ParentId equals p.Id into mp
                    from lmc in mc.DefaultIfEmpty()
                    from lmcl in mcl.DefaultIfEmpty()
                    from lmp in mp.DefaultIfEmpty()
                    select new PrincipalHotlineDto
                    {
                        Id = m.Id,
                        ChildId = m.ChildId,
                        ChildName = lmc.Name,
                        ChildImgId = lmc.ImgId,
                        ClassId = m.ClassId,
                        ClassName = lmcl.Name,
                        ParentId = m.ParentId,
                        ParentName = lmp.Name,
                        Relationship = m.Relationship,
                        CreatedTime = m.CreatedTime,
                        Content = m.Content,
                        IsReply = m.IsReply,
                        Images = m.Images,
                        ReplyList = m.ReplyList,
                    }).ToList();
        }

        /// <summary>
        /// 创建
        /// </summary>
        /// <returns></returns>
        public async Task<bool> CreateAsync(CreateOrUpdatePrincipalHotlineInput input)
        {
            if (_currentUser == null)
            {
                throw AppResultException.Status409Conflict("登录已过期,请重新登录!");
            }
            var userId = _currentUser?.FindClaimValue(SimpleClaimTypes.UserId);
            var relationship = _currentUser?.FindClaimValue(SimpleClaimTypes.Relationship);
            var childId = _currentUser?.FindClaimValue(SimpleClaimTypes.ChildId);
            var claccId = _currentUser?.FindClaimValue(SimpleClaimTypes.ClassesId);
            var images = new List<PrincipalHotlineImage>();
            if (input.ImageIdList != null)
            {
                var files = await _fileInfoService.GetFilesByIdListAsync(input.ImageIdList);
                images = files?.Select(file => new PrincipalHotlineImage { FiledId = file.Id, FileName = file.FileName, FileSize = file.FileSize ?? String.Empty })?.ToList();
            }
            var entity = new PrincipalHotline();
            entity.ChildId = new Guid(childId);
            entity.ClassId = new Guid(claccId);
            entity.ParentId = new Guid(userId);
            entity.Relationship = int.Parse(relationship);
            entity.Images = images;
            entity.Content = input.Content;

            await _context.AddAsync(entity);
            var rte = await _context.SaveChangesAsync();
            return rte > 0;
        }

        /// <summary>
        /// 回复
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        public async Task<bool> ReplyAsync(ReplyInput input)
        {
            var entity = await _context.Set<PrincipalHotline>().FirstOrDefaultAsync(p => p.Id == input.PrincipalHotlineId);
            if (entity == null)
            {
                throw AppResultException.Status500InternalServerError("没有找到该热线记录!");
            }
            entity.IsReply = true;
            _context.Update(entity);
            var userId = _currentUser?.FindClaimValue(SimpleClaimTypes.UserId);
            var userName = _currentUser?.FindClaimValue(SimpleClaimTypes.Name);
            var reply = new PrincipalHotlineReply()
            {
                ReplyUserId = new Guid(userId),
                ReplyUserName = userName,
                ReplyContent = input.ReplyContent,
                PrincipalHotlineId = input.PrincipalHotlineId
            };
            await _context.AddAsync(reply);
            return (await _context.SaveChangesAsync()) > 0;
        }

        public async Task<bool> DeleteAsync(Guid id)
        {
            var entity = await _context.Set<PrincipalHotline>().Include(p => p.Images).Include(p => p.ReplyList).FirstOrDefaultAsync(p => p.Id == id);
            if (entity == null)
            {
                throw AppResultException.Status500InternalServerError("没有找到该热线记录!");
            }
            var loginType = _currentUser?.FindClaimValue(SimpleClaimTypes.LoginType);
            if (loginType == "ParentSide" && entity?.IsReply == true)
            {
                throw AppResultException.Status500InternalServerError("不能删除已回复的建议!");
            }
            _context.Remove(entity);
            return await _context.SaveChangesAsync() > 0;
        }

        public async Task<bool> DeletReplyAsync(Guid id)
        {

            var entity = await _context.Set<PrincipalHotlineReply>().FirstOrDefaultAsync(p => p.Id == id);
            if (entity == null)
            {
                throw AppResultException.Status500InternalServerError("没有找到该热线回复记录!");
            }

            var hotline = await _context.Set<PrincipalHotline>().Include(p => p.ReplyList).FirstOrDefaultAsync(p => p.Id == entity.PrincipalHotlineId);

            if (hotline?.ReplyList?.Where(p => p.Id != id).Count() == 0)
            {
                hotline.IsReply = false;
                _context.Update(hotline);
            }
            _context.Remove(entity);
            return await _context.SaveChangesAsync() > 0;
        }
    }
}
